<?php

use App\Services\ICookieService;
use App\Services\ISessionService;

if(!function_exists('isMock'))
{
    /**
     * 判断是否开启模拟环境
     */
    function isMock(){
        return config('common.mock',false);
    }
}

if(!function_exists('getip'))
{
    function getip(){
        request()->setTrustedProxies(['172.0.0.0/8','192.0.0.0/8','127.0.0.0/8']);
        return request()->getClientIp();
    }
}

if(!function_exists('getAreas'))
{
    /**
     * 获取省市数据
     * @param string $key areas/provinceIds
     * @return array
     */
    function getAreas($key = 'areas'){
        static $areas;
        static $provinceIds;
        if ($areas === null){
            $source = @include_once(resource_path('static/areas.php'));
            $areas = @json_decode($source['areas'],true);
            $provinceIds = @json_decode($source['provinceIds'],true);
        }
        return !empty($$key) ? $$key : [];
    }
}

if(!function_exists('getCurrentUser'))
{
    /**
     * 获取当前用户
     * @return mixed
     */
    function getCurrentUser(){
        return resolve(ISessionService::class)->getCurrentUser();
    }
}

if(!function_exists('getCurrentUserid'))
{
    /**
     * 获取当前用户id
     * @return mixed
     */
    function getCurrentUserid(){
        return resolve(ICookieService::class)->currentUserid();
    }
}

if(!function_exists('getCurrentWeixinUserid'))
{
    /**
     * 获取当前微信用户成员id
     * @return mixed
     */
    function getCurrentWeixinUserid(){
        return resolve(ICookieService::class)->currentWeixinUserid();
    }
}

if(!function_exists('getCurrentWeixinUser'))
{
    /**
     * 获取当前微信企业号成员用户
     * @return mixed
     */
    function getCurrentWeixinUser(){
        return resolve(ISessionService::class)->getCurrentWeixinUser();
    }
}

if(!function_exists('uc_authcode'))
{
    /**
     * 来自ucenter的加/解密函数
     * @param string $string 要加/解密的字符串
     * @param enum $operation 操作类型，DECODE：解密，ENCODE：加密
     * @param string $key 自定义盐
     * @param int $expiry 加密结果过期时间
     * @return string
     */
    function uc_authcode($string, $operation = 'DECODE', $expiry = 0, $key = '') {
        $ckey_length = 4;

        $key = md5($key ? $key : config('app.key'));
        $keya = md5(substr($key, 0, 16));
        $keyb = md5(substr($key, 16, 16));
        $keyc = $ckey_length ? ($operation == 'DECODE' ? substr($string, 0, $ckey_length): substr(md5(microtime()), -$ckey_length)) : '';

        $cryptkey = $keya.md5($keya.$keyc);
        $key_length = strlen($cryptkey);

        $string = $operation == 'DECODE' ? base64_decode(substr($string, $ckey_length)) : sprintf('%010d', $expiry ? $expiry + time() : 0).substr(md5($string.$keyb), 0, 16).$string;
        $string_length = strlen($string);

        $result = '';
        $box = range(0, 255);

        $rndkey = array();
        for($i = 0; $i <= 255; $i++) {
            $rndkey[$i] = ord($cryptkey[$i % $key_length]);
        }

        for($j = $i = 0; $i < 256; $i++) {
            $j = ($j + $box[$i] + $rndkey[$i]) % 256;
            $tmp = $box[$i];
            $box[$i] = $box[$j];
            $box[$j] = $tmp;
        }

        for($a = $j = $i = 0; $i < $string_length; $i++) {
            $a = ($a + 1) % 256;
            $j = ($j + $box[$a]) % 256;
            $tmp = $box[$a];
            $box[$a] = $box[$j];
            $box[$j] = $tmp;
            $result .= chr(ord($string[$i]) ^ ($box[($box[$a] + $box[$j]) % 256]));
        }

        if($operation == 'DECODE') {
            if((substr($result, 0, 10) == 0 || substr($result, 0, 10) - time() > 0) && substr($result, 10, 16) == substr(md5(substr($result, 26).$keyb), 0, 16)) {
                return substr($result, 26);
            } else {
                return '';
            }
        } else {
            return $keyc.str_replace('=', '', base64_encode($result));
        }

    }
}

if(!function_exists('curl'))  
{
//    function scurl($url) {
//        $curl = curl_init();
//        curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
//        curl_setopt($curl, CURLOPT_TIMEOUT, 500);
//        curl_setopt($curl, CURLOPT_URL, $url);
//
//        $res = curl_exec($curl);
//        curl_close($curl);
//
//        return $res;
//    }
    
    /**
     * CURL
     * @param string $url 目标url地址
     * @param array|string $post post数据
     * @param int $timeout 超时
     * @param array|string $cookies cookie数组|字串
     * @param array|string $headers 头信息数组|字串
     * @param string $user_agent useragent字串
     * @param string $referer 来源url
     * @return string|boolean
     */
    function curl($url, $post = null, $timeout = 120, $cookies = null, $headers = null, $user_agent = null, $referer = null) {
        if (!$url)
            return false;
        $init = curl_init();
        //curl_setopt($init, CURLOPT_HEADER, 1);
        //curl_setopt($init, CURLOPT_NOBODY, 1);
        curl_setopt($init, CURLOPT_URL, $url);
        curl_setopt($init, CURLOPT_RETURNTRANSFER, true);
        curl_setopt($init, CURLOPT_CONNECTTIMEOUT_MS, $timeout*1000);
        curl_setopt($init, CURLOPT_TIMEOUT_MS , $timeout*1000);
        curl_setopt($init, CURLOPT_SSL_VERIFYHOST, 0);
        curl_setopt($init, CURLOPT_SSL_VERIFYPEER, 0);
        //curl_setopt($init, CURLOPT_USERAGENT, "Mozilla/5.0 (Windows; U; Windows NT 6.0; en-US; rv:1.9.2.2) Gecko/20100316 Firefox/3.6.2 (.NET CLR 3.5.30729)");
        curl_setopt($init, CURLOPT_FOLLOWLOCATION, 1); // 使用自动跳转
        if ($post) {
            curl_setopt($init, CURLOPT_POST, true);
            if (is_array($post) || is_string($post))
                curl_setopt($init, CURLOPT_POSTFIELDS, $post);
        }
        if ($cookies) {
            if (is_array($cookies))
                $cookies = http_build_cookie($cookies);
            if (is_string($cookies) && strlen($cookies))
                curl_setopt($init, CURLOPT_COOKIE, $cookies);
        }
        if ($headers) {
            if (is_array($headers)){
                foreach ($headers as $k => $v){
                    if (is_string($k) && strlen($k)){
                        $headers[$k] = $k .': '. $v;
                    }elseif(!strpos(':',$v))
                        $headers[$k] = '';
                }
            }elseif(!strpos(':',$headers))
                $headers = '';
            if ($headers = array_filter((array)$headers));
                curl_setopt($init, CURLOPT_HTTPHEADER, $headers);
        }
        if (is_string($user_agent)){
            curl_setopt($init, CURLOPT_USERAGENT, $user_agent);
        }
        if (is_string($referer)){
            curl_setopt($init, CURLOPT_REFERER, $referer);
        }
        $result = curl_exec($init);
        if ($error = curl_errno($init))
            return false;
        //$http_code = curl_getinfo($init,CURLINFO_HTTP_CODE);
        //$header_size = curl_getinfo($init,CURLINFO_HEADER_SIZE);
        curl_close($init);
        return $result;
    }
}

if(!function_exists('curl_multi'))  {
    /**
     * CURL多并发
     *
     *  $urls = array(
     *
     *      //post数据
     *
     *      'post'=>array(
     *
     *          'name'=>'abc',
     *
     *          'get'=>true
     *
     *      ),
     *
     *      //超时时间，秒
     *
     *      'timeout'=>120,
     *
     *      //cookie数据
     *
     *      'cookies'=>'asos=userCountryIso=CN&topcatid=1000&currencyid=2&currencylabel=USD',
     *
     *      //header数据
     *
     *      '$headers'=>array(
     *
     *          'X-FORWARDED-FOR'=>'127.0.0.1',
     *
     *          'CLIENT-IP'=>'127.0.0.1'
     *
     *      ),
     *
     *      //useragent信息
     *
     *      'user_agent'=>'Mozilla/5.0 (Windows NT 6.1; Win64; x64; rv:16.0) Gecko/20121026 Firefox/16.0',
     *
     *      //请求来源信息
     *
     *      'referer'=>'http://127.0.0.1/',
     *
     *      CURLOPT_FOLLOWLOCATION=>0
     *
     *  );
     *
     * OR
     *
     *  $urls = array(
     *
     *      array(
     *
     *          'post'=>'asos=userCountryIso=CN&topcatid=1000&currencyid=2&currencylabel=USD',
     *
     *          'timeout'=>5,
     *
     *      ),
     *
     *      array(
     *
     *          CURLOPT_TIMEOUT=>5,
     *
     *          CURLOPT_TIMEOUT=>30,
     *
     *          'cookies'=>'asos=userCountryIso=CN&topcatid=1000&currencyid=2&currencylabel=USD',
     *
     *          'headers'=>'X-FORWARDED-FOR:127.0.0.1',
     *
     *      ),
     *
     *      array(
     *
     *          CURLOPT_HEADER=>1,
     *
     *          'user_agent'=>'Mozilla/5.0 (Windows NT 6.1; Win64; x64; rv:16.0) Gecko/20121026 Firefox/16.0',
     *
     *          'referer'=>'http://127.0.0.1/'
     *
     *      )
     *
     *  );
     * @param array $urls 要请求的url地址数组
     * @param array $options curl请求选项
     * @return array
     */
    function curl_multi(array $urls, array $options = null) {
        if (empty($urls))
            return false;
        $init = curl_multi_init();
        $default_option = array(
            //启用时会将头文件的信息作为数据流输出
            CURLOPT_HEADER => 0,
            //文件流形式
            CURLOPT_RETURNTRANSFER => 1,
            //设置curl允许执行的最长秒数
            CURLOPT_TIMEOUT => 5,
            CURLOPT_CONNECTTIMEOUT => 5,
            //SSL安全验证
            CURLOPT_SSL_VERIFYHOST => 0,
            CURLOPT_SSL_VERIFYPEER => 0,
            //自动跳转
            CURLOPT_FOLLOWLOCATION => 1
        );

        $options = (array)$options;
        if (array_keys($options) !== range(0,count($options)-1)){
            $options = array_fill(0,count($urls),$options);
        }

        foreach ($options as $i=>$option){

            if (isset($option['timeout'])) {
                $timeout = $option['timeout'];
                if ($timeout){
                    $option[CURLOPT_CONNECTTIMEOUT_MS] = $timeout*1000;
                    $option[CURLOPT_TIMEOUT_MS] = $timeout*1000;
                }
                unset($option['timeout']);
            }
            if (isset($option['post'])) {
                $post = $option['post'];
                if ($post){
                    $option[CURLOPT_POST] = true;
                    if (is_array($post) || is_string($post))
                        $option[CURLOPT_POSTFIELDS] = $post;
                }
                unset($option['post']);
            }
            if (isset($option['cookies'])) {
                $cookies = $option['cookies'];
                if ($cookies){
                    if (is_array($cookies))
                        $cookies = http_build_cookie($cookies);
                    if (is_string($cookies) && strlen($cookies))
                        $option[CURLOPT_COOKIE] = $cookies;
                }
                unset($option['cookies']);
            }
            if (isset($option['headers'])) {
                $headers = $option['headers'];
                if ($headers){
                    if (is_array($headers)){
                        foreach ($headers as $k => $v){
                            if (is_string($k) && strlen($k)){
                                $headers[$k] = $k .': '. $v;
                            }elseif(!strpos(':',$v))
                                $headers[$k] = '';
                        }
                    }elseif(!strpos(':',$headers))
                        $headers = '';
                    if ($headers = array_filter((array)$headers));
                    $option[CURLOPT_HTTPHEADER] = $headers;
                }
                unset($option['headers']);
            }
            if (isset($option['user_agent'])) {
                $user_agent = $option['user_agent'];
                if (is_string($user_agent)){
                    $option[CURLOPT_USERAGENT] = $user_agent;
                }
                unset($option['user_agent']);
            }
            if (isset($option['referer'])) {
                $referer = $option['referer'];
                if (is_string($referer)){
                    $option[CURLOPT_REFERER] = $referer;
                }
                unset($option['referer']);
            }

            $options[$i] = $option;
        }

        $conn = array();
        foreach ($urls as $k => $url) {
            if (!empty($url)){
                $ch = curl_init($url);
                $option = !empty($options[$k]) ? ($options[$k] + $default_option) : $default_option;
                @curl_setopt_array($ch, $option);
                curl_multi_add_handle($init, $ch);
                $conn[$k] = $ch;
            }else{
                $conn[$k] = null;
            }
        }

        do{
            do {
                $mrc = curl_multi_exec($init, $running);
                usleep(10000);
            } while (($mrc == CURLM_CALL_MULTI_PERFORM) || (curl_multi_select($init) != -1));
        }while ($running and $mrc == CURLM_OK);

        $ret = array();
        foreach ($urls as $k => $url) {
            if (!empty($url)){
                $ch = $conn[$k];
                $error = curl_error($ch);
                $ret[$k] = $error ? false : curl_multi_getcontent($ch);
                curl_multi_remove_handle($init, $ch);
                curl_close($ch);
            }else{
                $ret[$k] = null;
            }
        }
        curl_multi_close($init);
        return  $ret;
    }
}

if(!function_exists('random'))  {
    /**
    * 返回随机字符串，数字/大写字母/小写字母
    * @param int $len 长度
    * @param enum $format 格式，ALL：英文字符+数字，CHAR：仅英文字符，UCNUMBER：大写英文字符+数字，LCNUMBER：小写英文字符+数字，NUMBER：仅数字，PNUMBER仅正数数字
    * @return string
    */
   function random($len = 6, $format = 'ALL') {
       switch (strtoupper($format)) {
           case 'ALL' :
               $chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
               break;
           case 'CHAR' :
               $chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz';
               break;
           case 'UCNUMBER' :
               $chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ123456789';
               break;
           case 'LCNUMBER' :
               $chars = 'abcdefghijklmnopqrstuvwxyz123456789';
               break;
           case 'NUMBER' :
               $chars = '0123456789';
               break;
           case 'PNUMBER' :
               $chars = '123456789';
               break;
           default :
               $chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
               break;
       }
       $string = "";
       while ( strlen ( $string ) < $len )
           $string .= substr ( $chars, (mt_rand () % strlen ( $chars )), 1 );
       return $string;
   }
}

/**
 * 弹出提示
 * @param string $msg 提示文字
 * @param string $url 弹出提示后跳转页面
 */
if(!function_exists('alert'))  {
    function alert($msg = null, $url = null) {
        $session_key = 'alert_message';
        headers_sent() or header('Content-type: text/html; charset=utf-8');
        if (($msg === null) && ($url === null)) {
            if ($alert = session($session_key)){
                echo '<script>alert("' . $alert . '");</script>';
            }
            session([$session_key=>'']);
            return true;
        }
        if ($url){
            session([$session_key=>$msg]);
        }else{
            echo '<script>alert("' . $msg . '");</script>';
        }
        if ($url) {
            echo '<script>location.href="' . $url . '";</script>';
            exit;
        }
    }
}

/**
 * 延迟跳转
 * @param string $url 跳转地址
 * @param int $timeout 延迟时间，秒为单位
 * @param string $msg 跳转前显示的提示文字
 */
if(!function_exists('delay'))  {
    function delay($url = '/',$timeout = 5,$msg = ''){
        $timeout = intval($timeout);
        if ($timeout <= 0){
            return error('wrong timeout setting <'.$timeout.'>');
        }
        headers_sent() or header('Content-type: text/html; charset=utf-8');
        if ($msg){
            echo "\r\n<br />",$msg;
        }
        echo <<<EOT
    <br />\r\n
    <span id="delaySecond">{$timeout}</span>秒后跳转......
    <script>var delay={$timeout};var delayer=setInterval(function(){
        document.getElementById("delaySecond").innerHTML=--delay;
        if (delay<=0) {location.href="{$url}";clearInterval(delayer);}
    },1000)</script>
EOT;
    }
}

/**
 * unicode解码
 * @param string $str unicode字符串
 * @return string
 */
if (!function_exists('unicodedecode')){
    function unicodedecode($str) {
        preg_match_all ( '/\\\u([[:alnum:]]{4})/', $str, $a );
        foreach ( $a [1] as $uniord ) {
            $dec = hexdec ( $uniord );
            $utf = '';
            if ($dec < 128) {
                $utf = chr ( $dec );
            } else if ($dec < 2048) {
                $utf = chr ( 192 + (($dec - ($dec % 64)) / 64) );
                $utf .= chr ( 128 + ($dec % 64) );
            } else {
                $utf = chr ( 224 + (($dec - ($dec % 4096)) / 4096) );
                $utf .= chr ( 128 + ((($dec % 4096) - ($dec % 64)) / 64) );
                $utf .= chr ( 128 + ($dec % 64) );
            }
            $str = str_replace ( '\u' . $uniord, $utf, $str );
        }
        return ($str);
    }
}